package cyy.example.com.facotry;

import java.lang.reflect.Field;
import java.lang.reflect.ParameterizedType;
import java.lang.reflect.Type;
import java.lang.reflect.WildcardType;
import java.util.List;

/**
 * Created by ChenYiYao on 2018/9/25.
 * des :
 */
public class Test {

    public static void main(String[] str) {
//        String str1 = "oeUsi7pu4u2l7L0attvQQMZkRecL2NFZHyMk3FQAHoHppe/jaopM2ATyFEeqhxNyJ/l8rEBmh12z\r\n4tJEdY+AHg==";
//        for (int i = 0, length = str1.length(); i < length; i++) {
//            System.out.print(str1.charAt(i));
//        }
//        System.out.println();
//        System.out.print(encodeHeadInfo(str1));
//        System.out.print("2018-10-14".compareTo("2018-10-13") + "-------------------");

        testWildCardType();
    }


    private static String encodeHeadInfo(String headInfo) {
        StringBuffer stringBuffer = new StringBuffer();
        for (int i = 0, length = headInfo.length(); i < length; i++) {
            char c = headInfo.charAt(i);
            if (c <= '\u001f' || c >= '\u007f') {
                stringBuffer.append(String.format("\\u%04x", (int) c));
            } else {
                stringBuffer.append(c);
            }
        }
        return stringBuffer.toString();
    }

    public class WildcardTypeBean {
        private List<? extends Number> a;  // a没有下界,
        //	没有指定的话，上边界默认是 Object ,下边界是 	String
        private List<? super String> b;

        private List<String> c;

        private Class<?> aClass;
    }


    public static void testWildCardType() {
        try {
            Field[] fields = WildcardTypeBean.class.getDeclaredFields();
            for (int i = 0; i < fields.length; i++) {
                Field field = fields[i];
                Type type = field.getGenericType();
                String nameString = field.getName();
                System.out.println("下面开始打印" + nameString + "是否具有通配符");
                if (!(type instanceof ParameterizedType)) {
                    System.out.print("!(type instanceof ParameterizedType)---------------------------");
                    continue;
                }
                ParameterizedType parameterizedType = (ParameterizedType) type;
                type = parameterizedType.getActualTypeArguments()[0];
                if (!(type instanceof WildcardType)) {
                    System.out.print("(type instanceof WildcardType)---------------------------");
                    continue;
                }
                WildcardType wildcardType = (WildcardType) type;
                Type[] lowerTypes = wildcardType.getLowerBounds();
                if (lowerTypes != null) {
                    System.out.print("下边界");
                    System.out.print("---------------------------");
                    System.out.println();
                    for (Type t : lowerTypes) {
                        System.out.print(t + ",");
                    }
                    System.out.println();
                    System.out.print("---------------------------");
                    System.out.println();
                }
                Type[] upTypes = wildcardType.getUpperBounds();
                if (upTypes != null) {
                    System.out.print("上边界");
                    System.out.println();
                    for (Type t : upTypes) {
                        System.out.print(t + ",");
                    }
                    System.out.println();
                }
                System.out.print("---------------------------");
            }
            Field fieldA = WildcardTypeBean.class.getDeclaredField("a");
            Field fieldB = WildcardTypeBean.class.getDeclaredField("b");
            // 先拿到范型类型
            System.out.print(fieldA.getGenericType() instanceof ParameterizedType);
            System.out.print(fieldB.getGenericType() instanceof ParameterizedType);
            ParameterizedType pTypeA = (ParameterizedType) fieldA.getGenericType();
            ParameterizedType pTypeB = (ParameterizedType) fieldB.getGenericType();
            // 再从范型里拿到通配符类型
            System.out.print(pTypeA.getActualTypeArguments()[0] instanceof WildcardType);
            System.out.print(pTypeB.getActualTypeArguments()[0] instanceof WildcardType);
            WildcardType wTypeA = (WildcardType) pTypeA.getActualTypeArguments()[0];
            WildcardType wTypeB = (WildcardType) pTypeB.getActualTypeArguments()[0];
            // 方法测试
            System.out.println(wTypeA.getUpperBounds()[0]);
            System.out.println(wTypeB.getLowerBounds()[0]);
            // 看看通配符类型到底是什么, 打印结果为: ? extends java.lang.Number
            System.out.println(wTypeA);
        } catch (NoSuchFieldException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (SecurityException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }

    }


}
